﻿// Original author contact info: Owen Emlen (owene_1998@yahoo.com)
// Note: other individuals may also have contributed to this code
// Project hosted on CodePlex.com as of 1/10/2009 at http://www.codeplex.com/EmlenMud
using System.Runtime.Serialization;
using System;
using System.Xml.Serialization;
using System.Threading;
using System.Reflection;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using BrainTechLLC.ThreadSafeObjects;

namespace BrainTechLLC
{
    public class NotifyCommand : Command, ICommandInfo
    {
        public override string HelpText { get { return "Subscribe or unsubscribe to notifications"; } }

        [NonSerialized, XmlIgnore]
        public static List<string> Words = new List<string>() { "NOTIFICATIONS", "NOTIFY" };

        public override List<string> FirstWords { get { return Words; } }

        [MethodVisible]
        public static List<PerceivedEventAndAudience> PerformMethod(CommandToPerform cmd, IGameThing source, IGameThing target, PropertyData args, PropertyData modifyingArguments)
        {
            List<PerceivedEventAndAudience> events = new List<PerceivedEventAndAudience>();
            GameChar sourceChar = source as GameChar;

#if NO_SILVERLIGHT
            GlobalLogger.Log("ABC", "This is the messagE", LogSeverity.Information);

            if (!string.IsNullOrEmpty(cmd.UserInput))
            {
                string[] strings = cmd.UserInput.Split(' ');
                Subscription sub = Subscription.None;

                foreach (string s in strings)
                {
                    Subscription sev = s.CreateEnum<Subscription>();
                    sub |= sev;
                }

                sourceChar.Subscriptions.Subscribe(sub, OnOffToggle.Toggle);
            }

            string output = typeof(Subscription).ShowValues((int)sourceChar.Subscriptions.Subscribed).BuildList((s) => s);
            events.Add(PerceivedEventAndAudience.ToChar(sourceChar.AssociatedID, output));

#endif
            return events;
        }
    }

#if NO_SILVERLIGHT
    public static class EnumExt
    {
        public static bool IsSet(this Subscription subscription, Subscription val)
        {
            return ((subscription & val) == val);
        }

        public static List<string> AllValues(this Type t)
        {
            List<string> results = new List<string>();
            var vals = Enum.GetValues(t);
            foreach (var val in vals)
            {
                results.Add(val.ToString());
            }
            return results;
        }

        public static List<string> ShowValues(this Type t, int value)
        {
            List<string> results = new List<string>();
            var vals = Enum.GetValues(t);
            foreach (var val in vals)
            {
                int v = (int)val;

                if ((v & value) == v)
                    results.Add("ON  " + val.ToString());
                else
                    results.Add("OFF " + val.ToString());
            }
            return results;
        }

        public static int EnumValue(this Type t, string s)
        {
            try
            {
                return (int)Enum.Parse(t, s, true);
            }
            catch
            {
                return 0;
            }
        }

        public static T CreateEnum<T>(this string s) where T : struct
        {
            int val = typeof(T).EnumValue(s);
            return (T)Enum.ToObject(typeof(T), val);
        }
    }
#endif

    public class EventListenerStub<T> where T : class
    {
        public event EventHandler<ObjectEventArgs<T>> EventOccurred;

        public EventListenerStub() { }

        public long AssociatedID { get; set; }

        public int EventHandlerCallCount { get; set; }

        public T LastMessage { get; private set; }

        public void OnEvent(object sender, ObjectEventArgs<T> ea)
        {
            this.EventHandlerCallCount++;
            this.LastMessage = ea.obj;

            if (EventOccurred != null)
                EventOccurred(sender, ea);
        }
    }
}
